﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using NETMovie.Entities;
using NETMovie.UI.WebMVC.Models;
using NETMovie.BLL;
using NETMovie.UI.WebMVC.Mappers;
using System.Text;
using System.IO;
using System.Configuration;

namespace NETMovie.UI.WebMVC.Controllers
{

    

    public class MovieController : Controller
    {
      

       
        //
        // GET: /ManageMovie/

        public ActionResult Index()
        {
            return View();
        }

     


      

        // **************************************
        // URL: /AddMovie
        // **************************************
        [Authorize]
        public ActionResult AddMovie()
        {

            MovieModel model = new MovieModel();

            MovieService movieService = new MovieService();
            IEnumerable<MovieCategory> movieCategoryList = movieService.GetCategories();
            Session["CategoryList"] = new MovieMapper().MapMovieCategories(movieCategoryList);

         


            return View(model);
        }
  

        [HttpPost]
        [Authorize]
        public ActionResult AddMovie(MovieModel model)
        {
            string fileName = String.Empty;
            String RandomMovieFileName = String.Empty;
            try
            {


                if (ModelState.IsValid)
                {

                    RandomMovieFileName = Guid.NewGuid().ToString();

                    if (Request.Files != null && Request.Files.Count > 0)
                    {

                        HttpPostedFileBase fileData = Request.Files[0];

                        // Notice how I save the file to App_Data\Uploads

                        StringBuilder filePath = new StringBuilder(Server.MapPath("~" + ConfigurationManager.AppSettings["UploadsPath"]));

                        string fileExt = "";

                        string[] tokens = fileData.FileName.Split(new char[] { '.' }, StringSplitOptions.RemoveEmptyEntries);

                        if (tokens != null && tokens.Length > 0)

                            fileExt = tokens[tokens.Length - 1];

                        if (fileExt != "mp4") ModelState.AddModelError("", "The input file must be .mp4 format");
                        else
                        {

                            // Notice that I use Guid.NewGuid to get a unique string for the file to be saved.
                            RandomMovieFileName += "." + fileExt;
                            filePath.Append(RandomMovieFileName);

                            fileName = filePath.ToString();
                            Response.Write(fileName);
                            fileData.SaveAs(fileName);

                        }
                    }



                    MovieMapper mapper = new MovieMapper();
                    NETMovie.Entities.Movie movie = mapper.Map(model, RandomMovieFileName);
                    //    catService = new CategoryService();

                    MovieService service = new MovieService();

                    int movieId = service.CreateMovie(movie);

                    FileInfo file = new FileInfo(fileName);

                    Response.Write(fileName);
                    return RedirectToAction("AddMovieResult", new { id = movieId });


                }
                return View(model);
            }
            catch 
            {

                if (!String.IsNullOrEmpty(fileName))
                {
                    FileInfo file = new FileInfo(fileName);
                    file.Delete();
                }
                
                return View(model);
            }
        }

        [Authorize]
        public ActionResult AddMovieResult(int id)
        {
            MovieService movieService = new MovieService();
            Movie movie = movieService.GetMovie(id);
            MovieModel movieModel  = new MovieMapper().ReMapDetail(movie);
            return View(movieModel);
        }

        [HttpPost]
        [Authorize]
        public ActionResult AddMovieResult(MovieModel movieModel, string AddMovieDetailButton)
        {
   
            switch(AddMovieDetailButton)
            {
                case "Add Castmembers":
            return RedirectToAction("AddMovieCastMembers", new { id = movieModel.MovieId });
               
                case "Add Article":
                    return  RedirectToAction("AddMovieArticle", new { id = movieModel.MovieId });
                case "Back":
                    return RedirectToAction("SearchMovie");
            }
            return View(movieModel);
        }

        [Authorize]
        public ActionResult AddMovieCastMembers(int id)
        {
            MovieService movieService = new MovieService();
            CastMember[] castMemberArr = movieService.GetMovieCastMembers(id);
            if (castMemberArr != null && castMemberArr.Length > 0)
            {
                return RedirectToAction("AddMovieResult", new { id = id });
            }


            CastMemberModel model = new CastMemberModel();
       
             //check if movieID exists in database
        
            Movie movie = movieService.GetMovie(id);
            if (movie == null)
            {
                ModelState.AddModelError("", "The movie does not exist");
                return RedirectToAction("AddMovie");
            }

            CastMemberModel[] CastMemberList = new CastMemberModel[15];

            List<SelectListItem> list = new List<SelectListItem>();
            list.Add(new SelectListItem { Text = "Actor", Value = "Actor" });
            list.Add(new SelectListItem { Text = "ScreenPlay", Value = "ScreenPlay" });
            list.Add(new SelectListItem { Text = "Director", Value = "Director" });
            Session["RoleList"] = list;
            CastMemberModel castMemberModel;
            for (int i = 0; i < CastMemberList.Length; i++)
            {
                castMemberModel = new CastMemberModel();
                castMemberModel.MovieId = id;
 
                CastMemberList[i] = castMemberModel;
             
            }

            MovieModel addModel = new MovieModel();
            addModel.MovieId = id;
            addModel.CastMembers = CastMemberList;
            return View(addModel);
        }

        [HttpPost]
        public ActionResult AddMovieCastMembers(MovieModel addmodel)
           
        {

            MovieService movieService = new MovieService();

           

           CastMemberModel [] modelList = addmodel.CastMembers;
          
            List<CastMember> CastMemberList = new List<CastMember>();
            foreach (var castmemberModel in modelList)
            {
                MovieMapper movieMapper = new MovieMapper();
                if (!string.IsNullOrEmpty(castmemberModel.Name) && (castmemberModel.Name.Trim().Length > 0))
                {
                    CastMember castMember = movieMapper.MapCastMember(castmemberModel);
                    CastMemberList.Add(castMember);
                }
            }

            int movieId = modelList[0].MovieId;
            movieService.AddMovieCastMember(CastMemberList, movieId);
            return RedirectToAction("AddMovieResult", new { id =movieId });

        }

        public ActionResult AddMovieArticle(int id)
        {
            MovieArticleModel artModel = new MovieArticleModel();
            artModel.MovieId = id;
            MovieService movieService = new MovieService();
       
            Article article = movieService.EditMovieArticle(id);
            if (article != null) { 
              return RedirectToAction("AddMovieResult", new { id = id });
            }
           
            return View(artModel);

        }

        [HttpPost]
        public ActionResult AddMovieArticle(MovieArticleModel movieArticleModel)
        {

            if (ModelState.IsValid)
            {
                MovieService movieService = new MovieService();
       
               Article article = new MovieMapper().mapArticle(movieArticleModel);

                movieService.AddMovieArticle(article, movieArticleModel.MovieId);
                return RedirectToAction("AddMovieResult", new { id = movieArticleModel.MovieId });
            }

            return View(movieArticleModel);
        }

        public ActionResult EditMovieArticle(int id)
        {
         
            

            MovieService movieService = new MovieService();
            Article article = movieService.EditMovieArticle(id);

            MovieArticleModel artModel = new MovieMapper().ReMapArticle(article, id);
           
            return View(artModel);

        }

        [HttpPost]
        public ActionResult EditMovieArticle(MovieArticleModel movieArticleModel)
        {

            if (ModelState.IsValid)
            {
                MovieService movieService = new MovieService();
                Article article = new MovieMapper().mapArticle(movieArticleModel);

                movieService.AddMovieArticle(article, movieArticleModel.MovieId);

                return RedirectToAction("EditMovieResult", new { id = movieArticleModel.MovieId });
            }
            return View(movieArticleModel);
        }


        // **************************************
        // URL: /UpdateMovie
        // **************************************

        public ActionResult EditMovie(string id)
        {
            MovieModel model = new MovieModel();
            MovieService movieService = new MovieService();

             IEnumerable<MovieCategory> movieCategoryList = movieService.GetCategories();
            Session["CategoryList"] = new MovieMapper().MapMovieCategories(movieCategoryList);

            Movie movie = movieService.GetMovie(Convert.ToInt16(id));
        
            MovieMapper movieMapper = new MovieMapper();
            model  = movieMapper.EditMovieReMap(movie);

            return View(model);
        
        }

        [HttpPost]
        public ActionResult EditMovie(MovieModel model)
        {
            string fileName = String.Empty;
            String RandomMovieFileName = String.Empty;

            try
            {


                if (ModelState.IsValid)
                {
                    RandomMovieFileName = Guid.NewGuid().ToString();

                    if (Request.Files != null && Request.Files.Count > 0)
                    {

                        HttpPostedFileBase fileData = Request.Files[0];

                        // Notice how I save the file to App_Data\Uploads

                        StringBuilder filePath = new StringBuilder(Server.MapPath("~/App_Data/Uploads/"));

                        string fileExt = "";

                        string[] tokens = fileData.FileName.Split(new char[] { '.' }, StringSplitOptions.RemoveEmptyEntries);

                        if (tokens != null && tokens.Length > 0)

                            fileExt = tokens[tokens.Length - 1];

                        if (fileExt != "mp4") ModelState.AddModelError("", "The input file must be .mp4 format");
                        else
                        {

                            // Notice that I use Guid.NewGuid to get a unique string for the file to be saved.

                            filePath.Append(fileName);

                            filePath.Append(".");

                            filePath.Append(fileExt);

                            fileName = filePath.ToString();
                            fileData.SaveAs(fileName);


                        }
                    }
                    // Attempt to register the user
                    MovieMapper mapper = new MovieMapper();
                    NETMovie.Entities.Movie movie = mapper.EditMovieMap(model,RandomMovieFileName);

                    MovieService service = new MovieService();

                    service.EditMovie(movie);

                }

                return RedirectToAction("EditMovieResult", new { id = model.MovieId });
             

            }
            catch
            {

                return View(model);
            }
        }

        public ActionResult EditMovieResult(int id)
        {
            MovieService movieService = new MovieService();
            Movie movie = movieService.GetMovie(id);
            MovieModel movieModel = new MovieMapper().ReMapDetail(movie);
            return View(movieModel);
        }

        [HttpPost]
        public ActionResult EditMovieResult(MovieModel movieModel, string EditMovieDetailButton)
        {

            switch (EditMovieDetailButton)
            {
                case "Edit Castmembers":
                    return RedirectToAction("EditMovieCastMembers", new { id = movieModel.MovieId });

                case "Edit Article":
                    return RedirectToAction("EditMovieArticle", new { id = movieModel.MovieId });
                case "Back":
                    return RedirectToAction("SearchMovie");
            }
            return View(movieModel);
        }


        public ActionResult DeleteMovie(int id)
        {
            MovieService movieService = new MovieService();
            Movie movie = movieService.GetMovie(id);
            MovieModel movieModel = new MovieMapper().ReMapDetail(movie);
            return View(movieModel);
        }

        [HttpPost]
        public ActionResult DeleteMovie(MovieModel movieModel, string DeleteMovieDetailButton)
        {

            switch (DeleteMovieDetailButton)
            {
                case "Confirm Delete":
                    MovieService movieService = new MovieService();
                    movieService.DeleteMovie(movieModel.MovieId);
                    return RedirectToAction("SearchMovie");
                    

                case "Cancel":
                    return RedirectToAction("SearchMovie");
            }
            return View(movieModel);
        }


        public ActionResult EditMovieCastMembers(int id)
        {
            MovieModel model = new MovieModel();
            try
            {

                MovieService movieService = new MovieService();
                Movie movie = movieService.GetMovie(id);
                CastMember[] CastMemberList = movieService.GetMovieCastMembers(id);

                CastMemberModel[] castMemberModelList = new MovieMapper().ReMapCastMember(CastMemberList, id);

                model.CastMembers = castMemberModelList;
                if (movie == null)
                {
                    ModelState.AddModelError("", "The movie does not exist");
                    return RedirectToAction("SearchMovie");
                }


                List<SelectListItem> list = new List<SelectListItem>();
                list.Add(new SelectListItem { Text = "Actor", Value = "Actor" });
                list.Add(new SelectListItem { Text = "ScreenPlay", Value = "ScreenPlay" });
                list.Add(new SelectListItem { Text = "Director", Value = "Director" });
                Session["RoleList"] = list;


                model.MovieId = id;
                model.CastMembers = castMemberModelList;
                return View(model);
            }
            catch (Exception e)
            {
                Response.Write(e.Message + "\n");
                Response.Write(e.InnerException + "\n");
                return View(model);
            }
        }

        [HttpPost]
        public ActionResult EditMovieCastMembers(MovieModel model)
        {
            CastMemberModel[] modelList = model.CastMembers;

            List<CastMember> CastMemberList = new List<CastMember>();
            foreach (var castmemberModel in modelList)
            {
                MovieMapper movieMapper = new MovieMapper();
                if (!string.IsNullOrEmpty(castmemberModel.Name) && (castmemberModel.Name.Trim().Length > 0))
                {
                    CastMember castMember = movieMapper.MapCastMember(castmemberModel);
                    CastMemberList.Add(castMember);
                }
            }

            MovieService movieService = new MovieService();
            int movieId = modelList[0].MovieId;
            movieService.EditMovieCastMembers(CastMemberList, movieId);
            return View("Index");

        }

        public ActionResult DeleteMovieCastMember(int id, int movieId)
        {
            MovieModel model = new MovieModel();
            try
            {
   
                MovieService movieService = new MovieService();
               movieService.DeleteMovieCastMember(id, movieId);

                return RedirectToAction("EditMovieCastMembers", new { id = movieId });
            }
            catch (Exception e)
            {
                Response.Write(e.Message + "\n");
                Response.Write(e.InnerException + "\n");
                return View(model);
            }
        }
        


              public ActionResult SearchMovie()
        {

            SearchMovieViewModel s = new SearchMovieViewModel();
            s.Results = new List<MovieModel>();
            MovieService service = new MovieService();
            MovieCategory[] movieCategoryList = service.GetCategories();
            Session["Category"] = new MovieMapper().MapMovieCategories(movieCategoryList);
           // Session["Category"] = 
            //Session["CastMember"] = GetCastMember();

            return View(s);
        }

        [HttpPost]
        public ActionResult SearchMovie(SearchMovieViewModel s, string SearchMoviePageButton)
        {
            try
            {
                MovieMapper mapper = new MovieMapper();

                Response.Write("button" + SearchMoviePageButton);
                switch (SearchMoviePageButton)
                {
                    // SearchMovieResultRecord searchRecordModel = new SearchMovieResultRecord();

                    case "Add Movie": return RedirectToAction("AddMovie");
                    case "Search Movie": IEnumerable<Movie> movieList;
                        MovieService service = new MovieService();

                        movieList = service.GetMovies(s.Title, s.Category, s.Keyword, true);


                        if (movieList == null) { movieList = new List<Movie>(); }
                        s.Results = mapper.ReMapSearchMovie(movieList);
                        return View(s);

                   
                }
                return View(s);
            }
            catch
            {
                return View(s);
            }
        }


        [HttpPost]
        public ActionResult AddUserComment(UserCommentModel viewModel)
        {

            UserComment userComment = new MovieMapper().CommentMap(viewModel);
                MovieService service = new MovieService();
                service.AddUserComment(viewModel.MovieId, userComment);
            
            return RedirectToAction("Index", new { MovieId = viewModel.MovieId, UserId = viewModel.UserId });
        }

        // **************************************
        // URL: /UpdateMovie
        // **************************************

        public ActionResult StreamMovie(string id)
        {
            
   //to add further functionalities in the method.

            return View();
        }

        // **************************************
        // URL: /DeleteMovie
        // **************************************
     //   [HttpPost]
        public ActionResult DeleteMovie(string id)
        {

            //to add further functionalities in the method.
            MovieService movieService = new MovieService();
            movieService.DeleteMovie(Convert.ToInt16(id));
            return RedirectToAction("SearchMovie");
        }


        /// <summary>
        /// 
        /// 
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public ActionResult ViewMovieDetails(int id)
        {
            MovieModel moviemodel = new MovieModel();

            MovieService service = new MovieService();
            NETMovie.Entities.Movie movie = service.GetMovie(id);
         //   bool isRented = service.IsRented(id);

            if (movie == null)
            {
              
                return RedirectToAction("SearchMovie", "Home");
            }

            MovieMapper mapper = new MovieMapper();


             moviemodel = mapper.ReMapDetail(movie);
            
            return View(moviemodel);
         
            }

    
    }
   
   
}
